package gui;

import javax.imageio.ImageIO;
import javax.swing.*;
import javax.swing.GroupLayout.*;

import java.awt.Color;
import java.awt.event.*;
import java.io.File;
import java.io.IOException;
import fn.Function;

public class PlotPanel extends JPanel {
	private static final long serialVersionUID = -616050500648048611L;

	public JToolBar toolBar;
	public JButton btnReset;
	public JToggleButton tglbtnAxes;
	public JToggleButton tglbtnTicks;
	public JToggleButton tglbtnGrid;
	public JPanel panel;
	public JButton btnHelp;
	public PlotCanvas canvas;
	public JToggleButton tglbtnNumbers;
	public JToggleButton tglbtnLegend;
	public JButton btnExport;

	public static void main(String[] args) throws Exception {
		UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
		JFrame f = new JFrame();
		f.setVisible(true);
		f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		PlotPanel p = new PlotPanel();
		p.addFn(Function.parse("0.000000255/x"));
		p.addFn(Function.parse("ln(2x)").derivative());
		f.getContentPane().add(p);
		f.pack();
	}

	public PlotPanel() {
		init();
	}

	private void init() {
		setFocusTraversalKeysEnabled(false);
		setRequestFocusEnabled(false);
		setFocusable(false);
		setSize(404, 432);
		canvas = new PlotCanvas(400, 400);
		canvas.setBorder(UIManager.getBorder("ScrollPane.border"));
		GroupLayout gl_plotCanvas = new GroupLayout(canvas);
		gl_plotCanvas.setHorizontalGroup(gl_plotCanvas.createParallelGroup(Alignment.LEADING).addGap(0, 405, Short.MAX_VALUE));
		gl_plotCanvas.setVerticalGroup(gl_plotCanvas.createParallelGroup(Alignment.LEADING).addGap(0, 405, Short.MAX_VALUE));
		canvas.setLayout(gl_plotCanvas);

		toolBar = new JToolBar();
		toolBar.setFocusTraversalKeysEnabled(false);
		toolBar.setRequestFocusEnabled(false);
		toolBar.setFocusable(false);
		toolBar.setFloatable(false);

		btnReset = new JButton(" + ");
		btnReset.setFocusTraversalKeysEnabled(false);
		btnReset.setRequestFocusEnabled(false);
		btnReset.setFocusable(false);
		btnReset.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				do_btnReset_actionPerformed(arg0);
			}
		});
		toolBar.add(btnReset);

		tglbtnAxes = new JToggleButton("Axes");
		tglbtnAxes.addMouseListener(new MouseAdapter() {
			@Override
			public void mouseClicked(MouseEvent paramMouseEvent) {
				do_tglbtnAxes_mouseClicked(paramMouseEvent);
			}
		});
		tglbtnAxes.setFocusTraversalKeysEnabled(false);
		tglbtnAxes.setRequestFocusEnabled(false);
		tglbtnAxes.setFocusable(false);
		tglbtnAxes.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				do_tglbtnAxes_actionPerformed(e);
			}
		});
		toolBar.add(tglbtnAxes);
		tglbtnAxes.setSelected(canvas._showAxis);

		tglbtnTicks = new JToggleButton("Ticks");
		tglbtnTicks.setFocusTraversalKeysEnabled(false);
		tglbtnTicks.setRequestFocusEnabled(false);
		tglbtnTicks.setFocusable(false);
		tglbtnTicks.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				do_tglbtnTicks_actionPerformed(e);
			}
		});
		toolBar.add(tglbtnTicks);
		tglbtnTicks.setSelected(canvas._showTick);

		tglbtnNumbers = new JToggleButton("Labels");
		tglbtnNumbers.addMouseListener(new MouseAdapter() {
			@Override
			public void mouseClicked(MouseEvent paramMouseEvent) {
				do_tglbtnNumbers_mouseClicked(paramMouseEvent);
			}
		});
		tglbtnNumbers.setFocusTraversalKeysEnabled(false);
		tglbtnNumbers.setRequestFocusEnabled(false);
		tglbtnNumbers.setFocusable(false);
		tglbtnNumbers.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				do_tglbtnNumbers_actionPerformed(e);
			}
		});
		toolBar.add(tglbtnNumbers);
		tglbtnNumbers.setSelected(canvas._showNum);

		tglbtnGrid = new JToggleButton("Grid");
		tglbtnGrid.addMouseListener(new MouseAdapter() {
			@Override
			public void mouseClicked(MouseEvent paramMouseEvent) {
				do_tglbtnGrid_mouseClicked(paramMouseEvent);
			}
		});
		tglbtnGrid.setFocusTraversalKeysEnabled(false);
		tglbtnGrid.setRequestFocusEnabled(false);
		tglbtnGrid.setFocusable(false);
		tglbtnGrid.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				do_tglbtnGrid_actionPerformed(e);
			}
		});
		toolBar.add(tglbtnGrid);
		tglbtnGrid.setSelected(canvas._showGrid);

		tglbtnLegend = new JToggleButton("Legend");
		tglbtnLegend.setFocusTraversalKeysEnabled(false);
		tglbtnLegend.setRequestFocusEnabled(false);
		tglbtnLegend.setFocusable(false);
		tglbtnLegend.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				do_tglbtnLegend_actionPerformed(e);
			}
		});
		toolBar.add(tglbtnLegend);
		tglbtnLegend.setSelected(canvas._showLgnd);

		panel = new JPanel();
		panel.setFocusTraversalKeysEnabled(false);
		panel.setRequestFocusEnabled(false);
		panel.setFocusable(false);
		toolBar.add(panel);
		GroupLayout gl_panel = new GroupLayout(panel);
		gl_panel.setHorizontalGroup(gl_panel.createParallelGroup(Alignment.LEADING).addGap(0, 297, Short.MAX_VALUE));
		gl_panel.setVerticalGroup(gl_panel.createParallelGroup(Alignment.LEADING).addGap(0, 21, Short.MAX_VALUE));
		panel.setLayout(gl_panel);

		btnHelp = new JButton(" ? ");
		btnHelp.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				do_btnHelp_actionPerformed(e);
			}
		});

		btnExport = new JButton("Export");
		btnExport.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				do_btnExport_actionPerformed(arg0);
			}
		});
		toolBar.add(btnExport);
		btnHelp.setFocusTraversalKeysEnabled(false);
		btnHelp.setRequestFocusEnabled(false);
		btnHelp.setFocusable(false);
		toolBar.add(btnHelp);
		GroupLayout groupLayout = new GroupLayout(this);
		groupLayout.setHorizontalGroup(groupLayout.createParallelGroup(Alignment.LEADING).addComponent(canvas, GroupLayout.DEFAULT_SIZE, 404, Short.MAX_VALUE)
				.addComponent(toolBar, GroupLayout.DEFAULT_SIZE, 404, Short.MAX_VALUE));
		groupLayout.setVerticalGroup(groupLayout.createParallelGroup(Alignment.LEADING).addGroup(
				groupLayout.createSequentialGroup().addComponent(canvas, GroupLayout.DEFAULT_SIZE, 409, Short.MAX_VALUE)
						.addComponent(toolBar, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)));
		setLayout(groupLayout);
	}

	protected void do_btnReset_actionPerformed(ActionEvent arg0) {
		if (canvas == null)
			return;
		canvas.resetView();
		canvas.repaint();
	}

	protected void do_tglbtnAxes_actionPerformed(ActionEvent e) {
		if (canvas == null)
			return;
		canvas._showAxis = tglbtnAxes.isSelected();
		canvas.repaint();
	}

	protected void do_tglbtnTicks_actionPerformed(ActionEvent e) {
		if (canvas == null)
			return;
		canvas._showTick = tglbtnTicks.isSelected();
		canvas.repaint();
	}

	protected void do_tglbtnGrid_actionPerformed(ActionEvent e) {
		if (canvas == null)
			return;
		canvas._showGrid = tglbtnGrid.isSelected();
		canvas.repaint();
	}

	protected void do_tglbtnNumbers_actionPerformed(ActionEvent e) {
		if (canvas == null)
			return;
		canvas._showNum = tglbtnNumbers.isSelected();
		canvas.repaint();
	}

	protected void do_tglbtnLegend_actionPerformed(ActionEvent e) {
		if (canvas == null)
			return;
		canvas._showLgnd = tglbtnLegend.isSelected();
		canvas.repaint();
	}

	protected void do_btnHelp_actionPerformed(ActionEvent e) {
		String msg = "";
		msg += "Pan - Left click and drag\n";
		msg += "To origin - Right click\n";
		msg += "Reset - Double right click\n";
		msg += "Zoom in - Mouse wheel up\n";
		msg += "Zoom out - Mouse wheel down\n";
		JOptionPane.showMessageDialog(this, msg);
	}

	public void addFn(Function fn) {
		canvas.addFn(fn);
	}

	public void removeFnAll() {
		canvas.removeFnAll();
	}

	protected void do_btnExport_actionPerformed(ActionEvent arg0) {
		JFileChooser fc = new JFileChooser();
		int c = fc.showSaveDialog(this);
		if (c == JFileChooser.APPROVE_OPTION)
			try {
				String s = fc.getSelectedFile().getAbsolutePath();
				if (!s.contains("png"))
					s += ".png";
				ImageIO.write(canvas.image, "png", new File(s));
			} catch (IOException e) {
				JOptionPane.showMessageDialog(this, "Couldn't export image.");
			}
	}

	protected void do_tglbtnAxes_mouseClicked(MouseEvent e) {
		if (e.getButton() == MouseEvent.BUTTON3) {
			Color c = JColorChooser.showDialog(this, "Choose a color for the axes.", canvas._colAxis);
			if (c != null)
				canvas._colAxis = c;
		}
		repaint();
	}

	protected void do_tglbtnNumbers_mouseClicked(MouseEvent e) {
		if (e.getButton() == MouseEvent.BUTTON3) {
			Color c = JColorChooser.showDialog(this, "Choose a color for the labels.", canvas._colNum);
			if (c != null)
				canvas._colNum = c;
		}
		repaint();
	}
	protected void do_tglbtnGrid_mouseClicked(MouseEvent e) {
		if (e.getButton() == MouseEvent.BUTTON3) {
			Color c = JColorChooser.showDialog(this, "Choose a color for the grid.", canvas._colGrid);
			if (c != null)
				canvas._colGrid = c;
		}
		repaint();
	}
}
